﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Security.Cryptography;
using System.IO;

namespace DGen
{



    /// <summary>
    /// Class containing static methods for generating checksum, hases, etc. 
    /// </summary>
    public class DCrypt
    {
        /// <summary>
        /// returns byte array of a MD5 hash.
        /// </summary>
        /// <param name="fileName"></param>
        /// <returns></returns>
        public static byte[] ComputeFileHash(string fileName)
        {
            using (var stream = File.OpenRead(fileName))
                return System.Security.Cryptography.MD5.Create().ComputeHash(stream);
        }
        /// <summary>
        /// Returns Unicode string of MD5 of file.
        /// </summary>
        /// <param name="fileName"></param>
        /// <returns></returns>
        public static string ComputeFileHashAsString(string fileName)
        {
            using (var stream = File.OpenRead(fileName))
            {
                byte[] hashB = System.Security.Cryptography.MD5.Create().ComputeHash(stream);
                return Encoding.UTF8.GetString(hashB).ToString();
            }

        }
        /// <summary>
        /// Returns ASCII string with MD5 hash in it.
        /// </summary>
        /// <param name="input"></param>
        /// <returns></returns>
        public static string ComputeHashAsString(string input)
        {
            byte[] hashB = Encoding.ASCII.GetBytes(input);
            byte[] hashB2 = System.Security.Cryptography.MD5.Create().ComputeHash(hashB);
            

            return Encoding.ASCII.GetString(hashB2).ToString();


        }


        /// <summary>
        /// Returns CRC32 checksum on a given string.
        /// </summary>
        /// <param name="inputString"></param>
        /// <returns></returns>
        public static string DiyChecksum(string inputString)
        {
            Crc32 c = new Crc32();
            byte[] b = Encoding.Default.GetBytes(inputString);
            return c.ComputeChecksum(b).ToString();
        }

        /// <summary>
        /// Basic class to generate CRC32 checksum. Based on some internet recipe, link current not to hand.
        /// </summary>
        public class Crc32
        {
            uint[] table;
            /// <summary>
            /// Returns checksum as unsigned int.
            /// </summary>
            /// <param name="bytes"></param>
            /// <returns></returns>
            public uint ComputeChecksum(byte[] bytes)
            {
                uint crc = 0xffffffff;
                for (int i = 0; i < bytes.Length; ++i)
                {
                    byte index = (byte)(((crc) & 0xff) ^ bytes[i]);
                    crc = (uint)((crc >> 8) ^ table[index]);
                }
                return ~crc;
            }
            /// <summary>
            /// Returns checksum as byte array
            /// </summary>
            /// <param name="bytes"></param>
            /// <returns></returns>
            public byte[] ComputeChecksumBytes(byte[] bytes)
            {
                return BitConverter.GetBytes(ComputeChecksum(bytes));
            }
            /// <summary>
            /// Default ctor.
            /// </summary>
            public Crc32()
            {
                uint poly = 0xedb88320;
                table = new uint[256];
                uint temp = 0;
                for (uint i = 0; i < table.Length; ++i)
                {
                    temp = i;
                    for (int j = 8; j > 0; --j)
                    {
                        if ((temp & 1) == 1)
                        {
                            temp = (uint)((temp >> 1) ^ poly);
                        }
                        else
                        {
                            temp >>= 1;
                        }
                    }
                    table[i] = temp;
                }
            }
        }

    }







}
